﻿using System;
using System.IO;
using System.Linq;
using System.Windows.Forms;

using Syncfusion.Windows.Forms;
using PMngr.Data;
using System.Collections.Generic;

namespace PMngr.Main
{
    public partial class SystemBackup : BaseControl
    {
        private IRepositoryFactory repositoryFactory;
        private string directoryPath = String.Empty;
        private string backupDBFile = String.Empty;

        public SystemBackup()
        {
            InitializeComponent();
        }

        public SystemBackup(IRepositoryFactory repositoryFactory)
            : this()
        {
            this.repositoryFactory = repositoryFactory;
        }

        private void btnBackup_Click(object sender, EventArgs e)
        {
            if (String.IsNullOrWhiteSpace(directoryPath))
            {
                MessageFactory.Show(Utilities.FirstBackupDir, MessageBoxIcon.Exclamation);
                return;
            }
            // copy to destination
            var dbFile = Application.StartupPath + @".\SQLCE4.sdf";
            var backupFile = directoryPath + String.Format(@"\SQLCE4_{0}.sdf", DateTime.Today.ToString("yyyyMMdd"));
            File.Copy(dbFile, backupFile, true);
            // compact
            var sqlCe = Application.StartupPath + @".\tools\SqlCeCmd40.exe";
            // sqlcecmd -d "Data Source=C:\Northwind.sdf" -e compact
            var proc = new System.Diagnostics.Process
                                                  {
                                                      StartInfo =
                                                          {
                                                              FileName = sqlCe,
                                                              Arguments =
                                                                  String.Format("-d \"Data Source={0}\" -e compact",
                                                                                backupFile),
                                                              CreateNoWindow = true,
                                                              UseShellExecute = false,
                                                              RedirectStandardOutput = true
                                                          }
                                                  };
            proc.Start();
            while (!proc.HasExited)
            {
                proc.WaitForExit(1000);
            }
            proc.Close();

            LogTrace(String.Format(Utilities.BackupCompleted, backupFile));
        }

        private void btnDirectory_Click(object sender, EventArgs e)
        {
            folderBrowser.StartLocation = FolderBrowserFolder.MyComputer;
            if (folderBrowser.ShowDialog() == DialogResult.OK)
            {
                txtDirectory.Text = folderBrowser.DirectoryPath;
                directoryPath = folderBrowser.DirectoryPath;                
            }

        }

        private void btnFile_Click(object sender, EventArgs e)
        {
            if (openFileDialog.ShowDialog() == DialogResult.OK && openFileDialog.CheckPathExists)
            {
                this.txtFile.Text = openFileDialog.FileName;
                //
                backupDBFile = openFileDialog.FileName;
            }       
        }

        private void btnRestore_Click(object sender, EventArgs e)
        {
            if (String.IsNullOrWhiteSpace(backupDBFile))
            {
                MessageFactory.Show(Utilities.FirstBackupFile, MessageBoxIcon.Exclamation);
                return;
            }

            if (MessageFactory.MessageBoxShow(Utilities.BackupConfirmed) == DialogResult.Yes)
            {
                // copy to destination
                var dbFile = Application.StartupPath + @".\SQLCE4.sdf";
                File.Copy(backupDBFile, dbFile, true);
                // restore
                var sqlCe = Application.StartupPath + @".\tools\SqlCeCmd40.exe";
                // sqlcecmd -d "Data Source=C:\Northwind.sdf" -e compact
                var proc = new System.Diagnostics.Process
                               {
                                   StartInfo =
                                       {
                                           FileName = sqlCe,
                                           Arguments = String.Format("-d \"Data Source={0}\" -e repairrecover", dbFile),
                                           CreateNoWindow = true,
                                           UseShellExecute = false,
                                           RedirectStandardOutput = true
                                       }
                               };
                proc.Start();
                while (!proc.HasExited)
                {
                    proc.WaitForExit(1000);
                }
                proc.Close();

                LogTrace(String.Format(Utilities.SuggestToRestart, dbFile));
            }

        }

        private void btnClear_Click(object sender, EventArgs e)
        {
            // TODO: find a good method to clear the unused items
            try
            {
                using (var repository = repositoryFactory.CreateRepository())
                {
                    // 选项
                    var options = repository.Find<ItemBase>(u => u.IsValid == false).ToList();
                    // check the references about these specified options
                    foreach (var option in options)
                    {
                        var temp = option;
                        repository.Delete<ItemBase>(u => u.Code == temp.Code);
                    }

                    repository.CommitChanges();
                }
            }
            catch (Exception) { }

            try
            {
                using (var repository = repositoryFactory.CreateRepository())
                {
                    // 1, 单位
                    var units = repository.Find<Unit>(u => u.IsValid == false && u.ParentUnit != null).ToList();
                    var result = new List<int>();

                    foreach (var unit in units)
                    {
                        var temp = unit;
                        var r1 = repository.Find<Profile>(p => p.InUnit.Id == temp.Id).ToList();
                        if (!r1.Any())
                        {
                            var r2 = repository.Find<Profile>(p => p.OutUnit.Id == temp.Id).ToList();
                            if (!r2.Any())
                                result.Add(temp.Id);
                        }
                    }
                    // delete the invalid unit
                    foreach (var id in result)
                    {
                        var temp = id;
                        repository.Delete<Unit>(u => u.Id == temp);
                    }

                    // 2, 主管部门
                    var upUnits = repository.Find<Unit>(u => u.IsValid == false && u.ParentUnit == null).ToList();
                    var invalidUpUnits = upUnits.Where(u => u.ChildUnits == null);
                    // delete the invalid unit
                    foreach (var unit in invalidUpUnits)
                    {
                        var temp = unit;
                        repository.Delete<Unit>(u => u.Id == temp.Id);
                    }

                    // 3, 整体划转数据 
                    var wholes = repository.Find<WholeTransfer>(w => w.Profiles.Count == 0).ToList();
                    foreach (var whole in wholes)
                    {
                        var temp = whole;
                        repository.Delete<WholeTransfer>(w => w.Id == temp.Id);
                    }

                    repository.CommitChanges();
                    LogTrace(Utilities.ClearInvalidData);
                }
            }
            catch (Exception) { }
        }
    }
}
